using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
using System.Runtime.InteropServices;

namespace ICode2
{
    public partial class Form1 : Form
    {
        [DllImport("umf.DLL", EntryPoint = "fw_init")]
        public static extern Int32 fw_init(Int16 port, Int32 baud);
        [DllImport("umf.DLL", EntryPoint = "fw_exit")]
        public static extern Int32 fw_exit(Int32 icdev);
        [DllImport("umf.Dll", EntryPoint = "fw_request")]
        public static extern Int32 fw_request(Int32 icdev, Byte _Mode, ref UInt32 TagType);
        [DllImport("umf.DLL", EntryPoint = "fw_anticoll")]
        public static extern Int32 fw_anticoll(Int32 icdev, Byte _Bcnt, ref UInt32 _Snr);
        [DllImport("umf.DLL", EntryPoint = "fw_select")]
        public static extern Int32 fw_select(Int32 icdev, UInt32 _Snr, ref Byte _Size);
        [DllImport("umf.DLL", EntryPoint = "fw_card")]
        public static extern Int32 fw_card(Int32 icdev, Byte _Mode, ref UInt32 _Snr);

        [DllImport("umf.DLL", EntryPoint = "fw_authentication")]
        public static extern Int32 fw_authentication(Int32 icdev, Byte _Mode, Byte _SecNr);
        [DllImport("umf.DLL", EntryPoint = "fw_halt")]
        public static extern Int32 fw_halt(Int32 icdev);
        [DllImport("umf.DLL", EntryPoint = "fw_beep")]
        public static extern Int32 fw_beep(Int32 icdev, UInt32 _Msec);
        [DllImport("umf.DLL", EntryPoint = "fw_reset")]
        public static extern Int16 fw_reset(IntPtr icdev, UInt16 _Msec);
        [DllImport("umf.DLL", EntryPoint = "hex_a")]
        public static extern void hex_a(ref Byte hex, ref Byte a, Int32 len);
        [DllImport("umf.dll", EntryPoint = "a_hex")]
        public static extern Int32 a_hex(ref Byte a, ref Byte hex, Int32 alen);

        [DllImport("umf.dll", EntryPoint = "fw_config_card")]
        public static extern Int32 fw_config_card(Int32 icdev, Byte cardtype);

        [DllImport("umf.dll", EntryPoint = "fw_inventory")]
        public static extern Int16 fw_inventory(Int32 icdev, Byte flags, Byte AFI, Byte masklen,
            ref Byte rlen, ref Byte rdata);
        [DllImport("umf.dll", EntryPoint = "fw_select_uid")]
        public static extern Int32 fw_select_uid(Int32 icdev, Byte flags, ref Byte UID);
        [DllImport("umf.dll", EntryPoint = "fw_reset_to_ready")]
        public static extern Int32 fw_reset_to_ready(Int32 icdev, Byte flags, ref Byte UID);
        [DllImport("umf.dll", EntryPoint = "fw_readblock")]
        public static extern Int16 fw_readblock(Int32 icdev, Byte flags, Byte startb, Byte numb, ref Byte UID,
            ref Byte rlen, ref Byte rdata);
        [DllImport("umf.dll",EntryPoint="fw_writeblock")]
        public static extern Int32 fw_writeblock(Int32 icdev, Byte flags, Byte startb, Byte numb, ref Byte UID,
             Byte rlen, ref Byte rdata);
        [DllImport("umf.dll", EntryPoint = "fw_get_securityinfo")]
        public static extern Int16 fw_get_securityinfo(Int32 icdev, Byte flags, Byte startb, Byte numb, ref Byte UID,
            ref Byte rlen, ref Byte rdata);


        bool isComOpen;
        int icdev;

        public Form1()
        {
            InitializeComponent();
        }

        private void btnClose_Click(object sender, EventArgs e)
        {
            this.Close();
        }

        private void Form1_Load(object sender, EventArgs e)
        {
            isComOpen = false;
            icdev = -1;

        }

        /// <summary>
        /// Open/Close port
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void btnOpen_Click(object sender, EventArgs e)
        {
            if (!isComOpen)
            {
                icdev = fw_init(short.Parse(textBox1.Text),115200);
                if (icdev > 0)
                {
                    fw_beep(icdev, 10);
  
                    listBox1.Items.Add("Open device success");

                    fw_config_card(icdev, 0x31);//set card type

                    isComOpen = true;
                    btnOpen.Text = "Close device";
                }
                else
                {
                    listBox1.Items.Add("Open device failed");

                }

            }
            else 
            {
                fw_exit(icdev);
                icdev = -1;
                btnOpen.Text = "Open device";

            }

        }

        private void button5_Click(object sender, EventArgs e)
        {
            listBox1.Items.Clear();
        }
        /// <summary>
        /// find single card
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void button3_Click(object sender, EventArgs e)
        {

            Int16 st;
            byte[] rlen = new byte[17];
            byte[] rbuffer = new byte[256];
            byte[] szRbuf = new byte[256];

            st = fw_inventory(icdev, 0x36, 0, 0, ref rlen[0], ref rbuffer[0]);        //find single card
            if (st != 0)
            {
                listBox1.Items.Add("Find single card ERROR!");
                return;
            }

            hex_a(ref szRbuf[0], ref rbuffer[0],2*rlen[0] );

            listBox1.Items.Add("Find single card Ok!");
            listBox1.Items.Add(Encoding.ASCII.GetString(szRbuf));
        }

        private void btnMulCard_Click(object sender, EventArgs e)
        {
            int st;
            byte[] rlen = new byte[17];
            byte[] rbuffer = new byte[256];
            st = fw_inventory(icdev, 0x16, 0, 0, ref rlen[0], ref rbuffer[0]);        //find single card
            if (st != 0)
            {
                listBox1.Items.Add("Find Multi card ERROR!");
                return;
            }
            listBox1.Items.Add("Find Multi card Ok!");
            listBox1.Items.Add(Encoding.ASCII.GetString(rbuffer));
        }

        //read card
        private void button1_Click(object sender, EventArgs e)
        {
            int st=0;
            byte[] UID = new byte[256];
            byte[] rlen = new byte[256];
            byte[] rbuffer = new byte[256];
            st = fw_inventory(icdev, 0x36, 0, 0, ref rlen[0], ref UID[0]);//0x36
            if (st != 0)
            {
                listBox1.Items.Add("ERROR1!");
                return;
            }

            st = fw_select_uid(icdev, 0x22, ref UID[0]);
            if (st != 0)
            {
                listBox1.Items.Add("ERROR3!");
                return;
            }

            st = fw_reset_to_ready(icdev, 0x22, ref UID[0]);
            if (st != 0)
            {
                listBox1.Items.Add("ERROR4!");
                return;
            }


            st = fw_get_securityinfo(icdev, 0x22, 0x04, 0x02, ref UID[0], ref rlen[0], ref rbuffer[0]);
            if (st != 0)
            {
                listBox1.Items.Add("ERROR5!");
                return;
            }


            int m_StaAddr = int.Parse(textBox2.Text);
            int m_Blockno = int.Parse(textBox3.Text);

            st = fw_readblock(icdev, 0x22, (byte)m_StaAddr, (byte)m_Blockno, ref UID[0], ref rlen[0], ref rbuffer[0]);  //read block data
            if (st != 0)
            {
                listBox1.Items.Add("Read data ERROR!");
                return;
            }


            for (int i = 0; i < m_Blockno; i++)
            {
                string tmp = "";
                if (m_StaAddr + m_Blockno > 28)
                {
                    m_Blockno = m_Blockno - ((m_StaAddr + m_Blockno) - 28);
                }

                tmp += "BlockAddr: [" + (m_StaAddr + i).ToString("d2") + "] Data: [" + rbuffer[i * 4].ToString("x2") + rbuffer[i * 4 + 1].ToString("x2") + rbuffer[i * 4 + 2].ToString("x2") + rbuffer[i * 4 + 3].ToString("x2")+"]";
                
                listBox1.Items.Add(tmp);
            }

        }
        //write card
        private void btnWrite_Click(object sender, EventArgs e)
        {

            int st;
            byte[] rlen = new byte[256];
            byte[] UID = new byte[256];
            byte[] WriteBuf = new byte[256];
            byte[] hexbuf = new byte[256];
            hexbuf = Encoding.ASCII.GetBytes(textBox4.Text);
            int m_StaAddr = int.Parse(textBox2.Text);

            int len = textBox4.Text.Length;
            if (len != 8)
            {
                MessageBox.Show("Length Error!");
                return;
            }

            st = fw_inventory(icdev, 0x36, 0, 0, ref rlen[0], ref UID[0]);//0x36
            if (st != 0)
            {
                listBox1.Items.Add("ERROR1!");
                return;
            }

            if (a_hex(ref WriteBuf[0], ref hexbuf[0], len / 2) != 0)
            {
                MessageBox.Show("ERROR1!");
                return;
            }

            st = fw_writeblock(icdev, 0x22, (byte)m_StaAddr, 1, ref UID[0], 4, ref WriteBuf[0]);

            if (st != 0)
            {
                listBox1.Items.Add("Write data ERROR!");
                return;
            }
            else
            {
                listBox1.Items.Add("Write data OK!");
            }

        }
    }
}